<?php

namespace app\api\service;

use app\api\model\Order as OrderModel;
use app\api\model\Product as ProductModel;
use app\api\model\OrderProduct;
use app\api\model\UserAddress;
use app\lib\exception\AddressException;
use think\Db;

class Order{

    private $oProducts;
    private $uid;
    private $products;

    public function place($uid,$oProducts)
    {
        $this->oProducts = $oProducts;
        $this->uid = $uid;
        $this->products = $this->getProductsByOrder($oProducts);
        // 检测库存
        $order = $this->getOrderStatus();
        if(!$order['pass']){
            $order['id'] = -1;
            return $order;
        }
        $orderSnap = $this->createOrderSnap($order);
        return $this->createOrderByTrans($orderSnap);
    }

    /* 获取数据库商品信息 */
    private function getProductsByOrder($oProducts)
    {
        $oPIDs = [];
        foreach($oProducts as $oProduct){
            array_push($oPIDs,$oProduct['product_id']);
        }
        $products = ProductModel::all($oPIDs);
        return $products;
    }

    /* 获取订单状态 */
    private function getOrderStatus()
    {
        $orderStatus = [
            'totalPrice' => 0,
            'totalCount' => 0,
            'pass' => true,
            'pStatusArray' => [],
        ];
        /* 进行库存校验并返回商品信息 */
        foreach($this->products as $product){
            $pStatusArray = $this->getProductStatus($product);
            $orderStatus['totalPrice'] += $pStatusArray['totalPrice'];
            $orderStatus['totalCount'] += $pStatusArray['count'];
            if($pStatusArray['havaStock']){
                $orderStatus['pass'] = false;
            }
            array_push($orderStatus['pStatusArray'],$pStatusArray);
        }
        return $orderStatus;
    }

    /* 获取商品状态 */
    private function getProductStatus($product)
    {
        $oProducts = $this->oProducts;
        $pIndex = -1;
        $pStatus = [
            'id' => null,
            'totalPrice' => 0,
            'count' => 0,
            'havaStock' => false,
            'name' => '',
        ];
        for($i = 0;$i<count($oProducts);$i++){
            if($oProducts[$i]['product_id']==$product['id']){
                $pIndex = $i;
            }
        }
        if($pIndex != -1){
            $product['havaStock'] = true;
        }
        $oProduct = $oProducts[$pIndex];
        $pStatus['id'] = $product['id'];
        $pStatus['totalPrice'] = $product['price'] * $oProduct['count'];
        $pStatus['count'] = $oProduct['count'];
        $pStatus['name'] = $product['name'];
        return $pStatus;
    }

    /* 获取用户地址 */
    public function getUserAddress()
    {
        $userAddress = UserAddress::getUserAddressByUID($this->uid);
        if(!$userAddress){
            throw new AddressException();
        }
        return $userAddress;
    }

    /* 创建订单快照 */
    private function createOrderSnap($order)
    {
        $orderSnap = [
            'totalPrice' => 0,
            'totalCount' => 0,
            'snapAddress' => '',
            'snapItems' => '',
            'snapImg' => '',
            'snapName' => '',
        ];

        $orderSnap['totalPrice'] = $order['totalPrice'];
        $orderSnap['totalCount'] = $order['totalCount'];
        $orderSnap['snapName'] = $this->products[0]['name'];
        $orderSnap['snapItems'] = json_encode($order['pStatusArray']);
        $orderSnap['snapImg'] = $this->products[0]['main_img_url'];
        $orderSnap['snapAddress'] = $this->getUserAddress();
        if(count($this->products) > 1){
            $orderSnap['snapName'] .= '等';
        }
        return $orderSnap;
    }

    /* 生成订单编号 */
    public static function makeOrderNo()
    {
        $yCode = array('A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J');
        $orderSn =
            $yCode[intval(date('Y')) - 2017] . strtoupper(dechex(date('m'))) . date(
                'd') . substr(time(), -5) . substr(microtime(), 2, 5) . sprintf(
                '%02d', rand(0, 99));
        return $orderSn;
    }
    
    /* 创建订单 */
    private function createOrderByTrans($orderSnap)
    {
        try{
            Db::startTrans();
            $order = new OrderModel();
            $orderProduct = new OrderProduct();
            $order->order_no = self::makeOrderNo();
            $order->total_price = $orderSnap['totalPrice'];
            $order->total_count = $orderSnap['totalCount'];
            $order->snap_name = $orderSnap['snapName'];
            $order->snap_img = $orderSnap['snapImg'];
            $order->snap_items = $orderSnap['snapItems'];
            $order->snap_address = $orderSnap['snapAddress'];
            $order->user_id = $this->uid;
            $order->save();
            foreach($this->oProducts as &$product){
                $product['order_id'] = $order->id;
            }
            $orderProduct->saveAll($this->oProducts);
            Db::commit();
            return [
                'create_time' => $order->create_time,
                'order_id' => $order->id,
                'order_no' => $order->order_no,
                'pass' => true,
            ];
        }catch(Exception $e){
            Db::rollback();
        }
    }

    /* 下单校验库存量 */
    public function checkOrderStatus($order_id)
    {
        $oProducts = OrderProduct::where('order_id',$order_id)->select();
        $this->oProducts = $oProducts;
        $this->products = $this->getProductsByOrder($oProducts);
        $order = $this->getOrderStatus();
        if(!$order['pass']){
            $order['id'] = -1;
        }
        return $order;
    }
    
}